package com.third.bank.service.impl;

import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.conditions.query.QueryWrapper;
import com.baomidou.mybatisplus.core.conditions.update.UpdateWrapper;
import com.baomidou.mybatisplus.core.conditions.query.LambdaQueryWrapper;
import com.baomidou.mybatisplus.core.toolkit.StringUtils;
import com.baomidou.mybatisplus.extension.service.impl.ServiceImpl;
import com.third.bank.entity.Balance;
import com.third.bank.entity.TotalAccounts;
import com.third.bank.entity.TransactionRecords;
import com.third.bank.entity.User;
import com.third.bank.mapper.BalanceMapper;
import com.third.bank.mapper.TotalAccountsMapper;
import com.third.bank.mapper.TransactionRecordsMapper;
import com.third.bank.mapper.UserMapper;
import com.third.bank.request.AddBalanceRequest;
import com.third.bank.request.ReduceBalanceRequest;
import com.third.bank.service.BalanceService;
import com.third.bank.service.UserService;
import com.third.bank.util.BaseResponse;
import com.third.bank.util.ErrorMessage;
import com.third.bank.util.MD5Util;
import com.third.bank.util.ResultUtils;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Service;
import org.springframework.transaction.annotation.Transactional;

import java.math.BigDecimal;
import java.time.LocalDateTime;
import java.util.Date;
import java.util.HashMap;
import java.util.Map;
import java.util.zip.DataFormatException;

import java.time.LocalDateTime;
import java.util.List;

/**
 * 余额serviceimpl
 */
@Service
public class BalanceServiceimpl extends ServiceImpl<BalanceMapper, Balance> implements BalanceService {

    @Autowired
    private BalanceMapper balanceMapper;

    @Autowired
    private UserService userService;

    @Autowired
    private UserMapper userMapper;

    @Autowired
    private TransactionRecordsMapper transactionRecordsMapper;

    @Autowired
    private TotalAccountsMapper totalAccountsMapper;

    @Override
    public void updateBatchUserBalance(List<Balance> balanceList) {
        balanceMapper.updateBatchUserBalance(balanceList);
    }

    @Override
    public List<Balance> getDailyUserList(LocalDateTime now) {
        LambdaQueryWrapper<Balance> wrapper = new LambdaQueryWrapper<>();
        wrapper.le(Balance::getUpdateTime, now);
        return list(wrapper);
    }

    @Override
    public Balance searchBalancebyID(Long id) {
        QueryWrapper<Balance> balanceQueryWrapper = new QueryWrapper<>();
        balanceQueryWrapper.eq("user_id", id);
        Balance balance = baseMapper.selectOne(balanceQueryWrapper);
        return balance;
    }


    @Override
    public int updateBalancebyID(Long id, Balance balance) {
        UpdateWrapper<Balance> balanceUpdateWrapper = new UpdateWrapper<>();
        balanceUpdateWrapper.eq("user_id", id);
        int i = baseMapper.update(balance,balanceUpdateWrapper);
        return i;
    }



    @Override
    @Transactional
    public BaseResponse addBalance(AddBalanceRequest addBalanceRequest) {
        //判断当前账户是否存在
        User user = userService.searchUserbycard(addBalanceRequest.getBankCard());
//        User user = userMapper.selectById(addBalanceRequest.getUserId());
        if(user == null){
            return  ResultUtils.error(ErrorMessage.CURRENT_USER_IS_NOT_EXIST);
        }
        String bankCard = user.getBankCard();
        System.out.println("bankcard:" + bankCard);
        // 用户输入的wdPassword加密后
        String wdPassword = MD5Util.getMD5(addBalanceRequest.getWdPassword());
        System.out.println("用户输入的wdPassword:" + wdPassword);
        System.out.println("数据库中的wdPassword:" + user.getWdPassword());
        //判断存款时的密码和账号是否输入
        if(StringUtils.isBlank(addBalanceRequest.getWdPassword())
                || StringUtils.isBlank(addBalanceRequest.getBankCard())){
            return  ResultUtils.error(ErrorMessage.PLEASE_INPUT_PASSWORD_OR_ACCOUNT);
        }
        //判断存款时输入的账号和密码是否正确
        if(!bankCard.equals(addBalanceRequest.getBankCard())
                || !wdPassword.equals(user.getWdPassword())){
            return  ResultUtils.error(ErrorMessage.ADD_MONEY_ACCOUNT_OR_PASSWORD_IS_FAIL);
        }
        //查询出账户信息
        Balance balance = balanceMapper.selectOne(new LambdaQueryWrapper<Balance>()
                .eq(Balance::getUserId, user.getId()));
        if(balance == null){
            return  ResultUtils.error(ErrorMessage.CURRENT_USER_HAS_NOT_ACCOUNT);
        }
        BigDecimal balance1 = balance.getBalance();
        BigDecimal transactionAmount = addBalanceRequest.getTransactionAmount();

        BigDecimal total = balance1.add(transactionAmount);

        //进行存款金额的变更
        balance.setBalance(total);
        balance.setUpdateTime(LocalDateTime.now());
        balanceMapper.updateById(balance);

        //增加交易记录
        TransactionRecords transactionRecords = new TransactionRecords();
        transactionRecords.setCreatedTime(LocalDateTime.now());
        transactionRecords.setUserId(user.getId());
        transactionRecords.setCounterpartName(user.getUsername());
        transactionRecords.setCounterpartAccount(user.getBankCard());
        transactionRecords.setAfterBalance(total);
        transactionRecords.setTransactionTime(LocalDateTime.now());
        transactionRecords.setTransactionAmount(transactionAmount);
        transactionRecords.setBusinessType(1);
        transactionRecordsMapper.insert(transactionRecords);


        //总账表修改
        TotalAccounts totalAccounts = new TotalAccounts();
        totalAccounts.setBalance(balance1);
        totalAccounts.setPostBalance(total);
        totalAccounts.setTransactionAmount(transactionAmount);
        totalAccounts.setTransactionDate(LocalDateTime.now());
        totalAccountsMapper.insert(totalAccounts);

        return ResultUtils.success(total);
    }

    @Override
    @Transactional
    public BaseResponse reduce(ReduceBalanceRequest reduceBalanceRequest) {
        //判断当前账户是否存在
//        User user = userMapper.selectById(reduceBalanceRequest.getUserId());
        User user = userService.searchUserbycard(reduceBalanceRequest.getBankCard());
        if(user == null){
            return  ResultUtils.error(ErrorMessage.CURRENT_USER_IS_NOT_EXIST);
        }
        //判断取款时的密码和账号是否输入
        String bankCard = user.getBankCard();

        //用户输入的付款密码
        String wdPassword = MD5Util.getMD5(reduceBalanceRequest.getWdPassword());
        System.out.println("用户输入的wdPassword:" + wdPassword);
        System.out.println("数据库中的wdPassword:" + user.getWdPassword());

        if(StringUtils.isBlank(reduceBalanceRequest.getWdPassword())
                || StringUtils.isBlank(reduceBalanceRequest.getBankCard())){
            return  ResultUtils.error(ErrorMessage.PLEASE_INPUT_PASSWORD_OR_ACCOUNT);
        }
        if(!bankCard.equals(reduceBalanceRequest.getBankCard())
                || !wdPassword.equals(user.getWdPassword())){
            return  ResultUtils.error(ErrorMessage.ADD_MONEY_ACCOUNT_OR_WDPASSWORD_IS_FAIL);
        }
        if (StringUtils.isBlank(reduceBalanceRequest.getWdPassword())
                || StringUtils.isBlank(reduceBalanceRequest.getWdPassword())){
            return ResultUtils.error(ErrorMessage.PLEASE_INPUT_WDPASSWORD_OR_ACCOUNT);
        }

        //查询出账户信息
        Balance balance = balanceMapper.selectOne(new LambdaQueryWrapper<Balance>()
                .eq(Balance::getUserId, user.getId()));
        if(balance == null){
            return  ResultUtils.error(ErrorMessage.CURRENT_USER_HAS_NOT_ACCOUNT);
        }

        BigDecimal balance1 = balance.getBalance();
        BigDecimal transactionAmount = reduceBalanceRequest.getTransactionAmount();
        if(transactionAmount.compareTo(balance1) == 1){
            return  ResultUtils.error(ErrorMessage.INSUFFICIENT_BALANCE);
        }
        //取款后剩余
        BigDecimal total = balance1.subtract(transactionAmount);


        balance.setUpdateTime(LocalDateTime.now());
        balance.setBalance(total);
        balanceMapper.updateById(balance);

        //增加交易记录
        TransactionRecords transactionRecords = new TransactionRecords();
        transactionRecords.setCreatedTime(LocalDateTime.now());
        transactionRecords.setUserId(user.getId());
        transactionRecords.setAfterBalance(total);
        transactionRecords.setCounterpartName(user.getUsername());
        transactionRecords.setCounterpartAccount(user.getBankCard());
        transactionRecords.setTransactionTime(LocalDateTime.now());
        transactionRecords.setTransactionAmount(transactionAmount);
        transactionRecords.setBusinessType(2);
        transactionRecordsMapper.insert(transactionRecords);


        //总账表修改
        TotalAccounts totalAccounts = new TotalAccounts();
        totalAccounts.setBalance(balance1);
        totalAccounts.setPostBalance(total);
        totalAccounts.setTransactionAmount(transactionAmount.negate());
        totalAccounts.setTransactionDate(LocalDateTime.now());
        totalAccountsMapper.insert(totalAccounts);

        return ResultUtils.success(total);
    }

    @Override
    public BaseResponse getBalanceByUserId(Long userId) {
        // 根据用户id查询余额``
        LambdaQueryWrapper<Balance> queryWrapper = new LambdaQueryWrapper<>();
        queryWrapper.eq(Balance::getUserId, userId);
        Balance balance = balanceMapper.selectOne(queryWrapper);

        // 判断如果结果不为空则返回查询到的余额值，为空则添加错误信息
        if (balance != null) {
            return ResultUtils.success(balance.getBalance());
        } else {
            return ResultUtils.error(ErrorMessage.NOT_FOUND_ERROR);
        }
    }
}
